﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Security;
using System.Web;

namespace Camalot.Common.Membership {
	// http://codefirstmembership.codeplex.com
	// Microsoft Public License (Ms-PL)
	// 
	// This license governs use of the accompanying software. If you use the software, you accept this license. 
	// If you do not accept the license, do not use the software.
	// 
	// 1. Definitions
	//
	// The terms "reproduce," "reproduction," "derivative works," and "distribution" have the same meaning here as 
	// under U.S. copyright law.
	// 
	// A "contribution" is the original software, or any additions or changes to the software.
	// 
	// A "contributor" is any person that distributes its contribution under this license.
	// 
	// "Licensed patents" are a contributor's patent claims that read directly on its contribution.
	// 
	// 2. Grant of Rights
	// 
	// (A) Copyright Grant- Subject to the terms of this license, including the license conditions and limitations 
	// in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free copyright license to 
	// reproduce its contribution, prepare derivative works of its contribution, and distribute its contribution 
	// or any derivative works that you create.
	// 
	// (B) Patent Grant- Subject to the terms of this license, including the license conditions and limitations in 
	// section 3, each contributor grants you a non-exclusive, worldwide, royalty-free license under its licensed 
	// patents to make, have made, use, sell, offer for sale, import, and/or otherwise dispose of its contribution 
	// in the software or derivative works of the contribution in the software.
	// 
	// 3. Conditions and Limitations
	// 
	// (A) No Trademark License- This license does not grant you rights to use any contributors' name, logo, or 
	// trademarks.
	// 
	// (B) If you bring a patent claim against any contributor over patents that you claim are infringed by the 
	// software, your patent license from such contributor to the software ends automatically.
	// 
	// (C) If you distribute any portion of the software, you must retain all copyright, patent, trademark, and 
	// attribution notices that are present in the software.
	// 
	// (D) If you distribute any portion of the software in source code form, you may do so only under this license 
	// by including a complete copy of this license with your distribution. If you distribute any portion of the 
	// software in compiled or object code form, you may only do so under a license that complies with this license.
	// 
	// (E) The software is licensed "as-is." You bear the risk of using it. The contributors give no express 
	// warranties, guarantees or conditions. You may have additional consumer rights under your local laws which 
	// this license cannot change. To the extent permitted under your local laws, the contributors exclude the 	
	// implied warranties of merchantability, fitness for a particular purpose and non-infringement.
	public sealed class WebSecurity {
		public static HttpContextBase Context {
			get { return new HttpContextWrapper ( HttpContext.Current ); }
		}

		public static HttpRequestBase Request {
			get { return Context.Request; }
		}

		public static HttpResponseBase Response {
			get { return Context.Response; }
		}

		public static System.Security.Principal.IPrincipal User {
			get { return Context.User; }
		}

		public static bool IsAuthenticated {
			get { return User.Identity.IsAuthenticated; }
		}

		public static MembershipCreateStatus Register ( string Username, string Password, string Email, bool IsApproved, string FirstName, string LastName ) {
			MembershipCreateStatus CreateStatus;
			System.Web.Security.Membership.CreateUser ( Username, Password, Email, null, null, IsApproved, null, out CreateStatus );

			if ( CreateStatus == MembershipCreateStatus.Success ) {
				using ( var Context = new DataContext ( ) ) {
					User User = Context.Users.FirstOrDefault ( Usr => Usr.Username == Username );
					User.FirstName = FirstName;
					User.LastName = LastName;
					Context.SaveChanges ( );
				}

				if ( IsApproved ) {
					FormsAuthentication.SetAuthCookie ( Username, false );
				}
			}

			return CreateStatus;
		}

		public enum MembershipLoginStatus {
			Success, Failure
		}

		public static MembershipLoginStatus Login ( string Username, string Password, bool RememberMe ) {
			if ( System.Web.Security.Membership.ValidateUser ( Username, Password ) ) {
				FormsAuthentication.SetAuthCookie ( Username, RememberMe );
				return MembershipLoginStatus.Success;
			} else {
				return MembershipLoginStatus.Failure;
			}
		}

		public static void Logout ( ) {
			FormsAuthentication.SignOut ( );
		}

		public static MembershipUser GetUser ( string Username ) {
			return System.Web.Security.Membership.GetUser ( Username );
		}

		public static bool ChangePassword ( string OldPassword, string NewPassword ) {
			MembershipUser CurrentUser = System.Web.Security.Membership.GetUser ( User.Identity.Name );
			return CurrentUser.ChangePassword ( OldPassword, NewPassword );
		}

		public static bool DeleteUser ( string Username ) {
			return System.Web.Security.Membership.DeleteUser ( Username );
		}

		public static List<MembershipUser> FindUsersByEmail ( string Email, int PageIndex, int PageSize ) {
			int totalRecords;
			return System.Web.Security.Membership.FindUsersByEmail ( Email, PageIndex, PageSize, out totalRecords ).Cast<MembershipUser> ( ).ToList ( );
		}

		public static List<MembershipUser> FindUsersByName ( string Username, int PageIndex, int PageSize ) {
			int totalRecords;
			return System.Web.Security.Membership.FindUsersByName ( Username, PageIndex, PageSize, out totalRecords ).Cast<MembershipUser> ( ).ToList ( );
		}

		public static List<MembershipUser> GetAllUsers ( int PageIndex, int PageSize ) {
			int totalRecords;
			return System.Web.Security.Membership.GetAllUsers ( PageIndex, PageSize, out totalRecords ).Cast<MembershipUser> ( ).ToList ( );
		}
	}
}
